package TestSystemClient;

import java.awt.*;

import javax.swing.*;
import javax.swing.border.*;
import javax.swing.table.DefaultTableModel;

import TestSystemIO.*;
import TestSystemUtil.*;

import java.awt.event.*;
import java.io.*;
import java.net.*;
import java.util.*;

@SuppressWarnings("serial")
public class ClientSinglePlayer extends JFrame {
	
	public Socket connection;
	public Protocol protocol = new Protocol();
	public ClientUtil util = new ClientUtil();
	public final Object writeLockObj = new Object();
	public final Object readLockObj = new Object();
	public InputThread inputThread;
	public OutputThread outputThread;
	
	public ArrayList<String> onlineUsers = new ArrayList<String>();
	public ArrayList<String> playerInfo = new ArrayList<String>();
	public ArrayList<String> questionInfo = new ArrayList<String>();
	public Vector<Vector<String>> tableRecord1 = new Vector<Vector<String>>();
	public Vector<Vector<String>> tableRecord2 = new Vector<Vector<String>>();
	public Vector<String> tableTitle1 = new Vector<String>();
	public Vector<String> tableTitle2 = new Vector<String>();
	public ArrayList<ArrayList<String>> groupInfo = new ArrayList<ArrayList<String>>(); 
	public String selected, hostname, questionField;
	public boolean inGroup = false;
	public int randomField, level;
	public Integer totalScore, score, ans; 
	
	
	public JPanel invitePanel, panelOnlineList, highScorePanel, gamePanel, levelPanel, startPanel, playPanel, panel, infoPanel,endPanel,historyPanel;
	public JLabel lblInvite, lblUsername, lblWhichLevelYou, lblQuestiontypelabel, lblWelcome, lblNamelabel, 
	lblEmailLabel, lblPhonelabel, svNameLabel, svPortLabel, clNameLabel, clPortLabel; 
	public JButton btnHistory, btnLogOut, btnExit, btnHighScore, btnStartGame, hsBackButton,  btnSubmit, btnHard,
	 btnMedium, btnEasy, btnInvite, btnAccept, btnDecline;
	public JRadioButton rdbtnChoiceA, rdbtnChoiceB, rdbtnChoiceC, rdbtnChoiceD;
	public JMenuItem mntmHowToPlay, mntmHighScore, mntmAbout, mntmExit, mntmNewGame;
	public JList<String> list;
	public JMenuBar menuBar;
	public JMenu mnGame, mnHelp;
	public JSeparator separator;
	public CardLayout cl = new CardLayout(0, 0);
	public JTextArea questionTextArea = new JTextArea();
	public JTable highScoreTable = new JTable();
	public JTable historyTable = new JTable();
	public JScrollPane scrollPane = new JScrollPane();
	public JPanel bgPanel = new JPanel() {
		public void paintComponent(Graphics g) {
			Image image = Toolkit.getDefaultToolkit().getImage(ClientLogin.class.getResource("/resources/background.jpg"));
			g.drawImage(image, 0, 0, image.getWidth(null), image.getHeight(null), this);
		}
	};
	public JScrollPane hsScrollPane,historyScrollPane;
	//private JPanel endPanel;
	private JLabel lblNewLabel_2;
	private JLabel lblQuestionsAnswered;
	private JLabel questionsAnsweredLabel;
	private JLabel lblScore;
	private JLabel lblFinalscore;
	private JButton btnBack;
	private JLabel lblCurrentScore;
	private JLabel lblCurrentscore;
	private JButton btnBack_1;

	//======== CLIENT SINGLE PLAYER FRAME CONSTRUCTOR =======//
	public ClientSinglePlayer(Socket conn) {

	//=== COPY SOCKET, TẠO INPUT + OUTPUT THREAD, PROTOCOL ==//
		connection = conn;											
		inputThread = util.makeInputThread(connection, readLockObj, protocol, this);
		outputThread = util.makeOutputThread(connection, writeLockObj);					
		util.startSession(inputThread, outputThread);
		protocol.setState(Protocol.SINGLEPLAY);
		//=======================================================//
		
		//============ KHỞI TẠO FRAME SINGLE PLAYER =============//
		createClientSinglePlayerFrame();						
		//=======================================================//
		
		//================ CLICK ABOUT BUTTON ===================//
		mntmAbout.addActionListener(new ActionListener() {
			public void actionPerformed(ActionEvent arg0) {
				ClientAbout clientAbout = new ClientAbout();
				clientAbout.setVisible(true);
			}
		});
		//=======================================================//

		//========== CLICK VÀO NUT EXIT TRÊN MENU BAR ===========//
		mntmExit.addActionListener(new ActionListener() {
			public void actionPerformed(ActionEvent e) {
				protocol.setState(Protocol.EXIT);							// STATE - EXIT
				Client.messageToServer = protocol.getMessageForm() + "\n";	// LẤY FORM MESSAGE
				synchronized(writeLockObj) {
					writeLockObj.notify();									// NOTIFY LẦN 1
				}
				try {
					Thread.sleep(100);										// SLEEP 0.1 S, MỤC ĐÍCH LÀ DO DÙNG 2 NOTIFY TRÊN CÙNG 1 OBJECT
				} catch (InterruptedException ex) {
					System.out.println("Menu bar - Exit (Sleep): " + ex);
				}
				protocol.setState(Protocol.SINGLEPLAY);						// STATE - SINGLEPLAY
				Client.messageToServer = "INTERRUPT" + "\n";				// GỬI TIN "INTERRUPT" ĐỂ INPUT STREAM THOÁT KHỎI HÀM READLINE
				synchronized(writeLockObj) {							
					writeLockObj.notify();									// NOTIFY LẦN 2
				}
				util.finishSession(inputThread, outputThread);				// ĐÓNG 2 THREAD INPUT VÀ OUTPUT
				ClientSinglePlayer.this.dispose();							// ĐÓNG FRAME LẠI
				try {
					connection.close();										// ĐÓNG SOCKET TỚI SERVER
				} catch (IOException ex) {
					System.out.println("Menu bar - Exit (close socket): " + ex);
				}
			} 
		});
		//=======================================================//
		
		//================ CLICK LOGOUT BUTTON ==================//
		btnLogOut.addMouseListener(new MouseAdapter() {
			public void mouseClicked(MouseEvent e) {
				protocol.setState(Protocol.LOGOUT);							// STATE - LOGOUT
				Client.messageToServer = protocol.getMessageForm() + "\n";	// LẤY FORM MESSAGE
				synchronized(writeLockObj) {
					writeLockObj.notify();									// NOTIFY LẦN 1 WRITELOCKOJB
				}
				try {	
					Thread.sleep(100);										// SLEEP 0.1 S ĐỂ DÙNG NOTIFY LẦN 2 TRÊN CÙNG 1 OBJECT
				} catch (InterruptedException e1) {
					
				}
				protocol.setState(Protocol.SINGLEPLAY);
				Client.messageToServer = "INTERRUPT" + "\n";
				synchronized(writeLockObj) {								// NOTIFY LẦN 2 TRÊN WRITELOCKOJB
					writeLockObj.notify();
				}
				util.finishSession(inputThread, outputThread);
				ClientSinglePlayer.this.dispose();
				new ClientLogin(connection).setVisible(true);
			}
		});
		//=======================================================//
		
		//================= CLICK ACCEPT BUTTON =================//
		btnAccept.addMouseListener(new MouseAdapter() {
			public void mouseClicked(MouseEvent e) {
				protocol.setState(Protocol.ACCEPT);
				Client.messageToServer = String.format(protocol.getMessageForm(), hostname) + "\n";
				synchronized(writeLockObj) {
					writeLockObj.notify();												// GỬI TIN ACCEPT TỚI HOST
				}
				inGroup = true;
				protocol.setState(Protocol.SINGLEPLAY);
				synchronized(readLockObj) {									
					try {
						readLockObj.wait();												// CHỜ THÔNG TIN CỦA GROUP TỪ SERVER SAU KHI ACCEPT
					} catch (InterruptedException ex) {
						System.out.println("Accept button (wait): " + ex);
					}
				}
				ClientMultiplayer clientMultiplayer = new ClientMultiplayer(connection);
				clientMultiplayer.setVisible(true);
				clientMultiplayer.setPlayerInfo(playerInfo);							// SET PLAYER INFO
				clientMultiplayer.setGroupInfo(groupInfo, hostname);					// SET GROUP INFO
				clientMultiplayer.setOnlineUsers(onlineUsers);							// SET ONLINE USERS
				clientMultiplayer.c.show(clientMultiplayer.panelPlay, "card2");			// CARD2 LÀ CARD CHO MEMBER CỦA MỘT GROUP KHI START
				Client.messageToServer = "INTERRUPT" + "\n";
				synchronized(writeLockObj) {
					writeLockObj.notify();
				}
				util.finishSession(inputThread, outputThread);
				ClientSinglePlayer.this.dispose();
			}
		});
		//=======================================================//
		
		//================ CLICK DECLINE BUTTON =================//
		btnDecline.addMouseListener(new MouseAdapter() {
			public void mouseClicked(MouseEvent e) {
				protocol.setState(Protocol.DECLINE);
				Client.messageToServer = String.format(protocol.getMessageForm(), hostname) + "\n";
				synchronized(writeLockObj) {
					writeLockObj.notify();
				}
				inGroup = false;
				hostname = null;
				protocol.setState(Protocol.SINGLEPLAY);	
			}
		});
		//=======================================================//
		
		//================ CLICK TRÊN ONLINE LIST ===============//
		list.addMouseListener(new MouseAdapter() {
			public void mouseClicked(MouseEvent e) {
				selected = list.getSelectedValue();
			}
		});
		//=======================================================//
		
		//================ CLICK INVITE BUTTON ==================//
		btnInvite.addMouseListener(new MouseAdapter() {
			public void mouseClicked(MouseEvent e) {
				protocol.setState(Protocol.INVITE);
				if(selected.equals(playerInfo.get(4))) {
					list.clearSelection();
					JOptionPane.showMessageDialog(null, "You can not invite yourself", "Warning", JOptionPane.WARNING_MESSAGE);
				} else if (selected.isEmpty()) {
					JOptionPane.showMessageDialog(null, "Choose an user", "Warning", JOptionPane.WARNING_MESSAGE);
				} else {
					Client.messageToServer = String.format(protocol.getMessageForm(), selected) + "\n";
					synchronized(writeLockObj) {
						writeLockObj.notify();
					}
				}
				protocol.setState(Protocol.SINGLEPLAY);
				synchronized(readLockObj) {
					try {
						readLockObj.wait();
					} catch (InterruptedException ex) {
						System.out.println("Invite (wait): " + ex);
					}
				}
				if(inputThread.result.get(0).equals("ACCEPT")) {
					synchronized(readLockObj) {
						try {
							readLockObj.wait();
						} catch (InterruptedException ex) { }
					}
					ClientMultiplayer clientMultiplayer = new ClientMultiplayer(connection);
					clientMultiplayer.setVisible(true);
					clientMultiplayer.setOnlineUsers(onlineUsers);
					clientMultiplayer.setPlayerInfo(playerInfo);
					hostname = playerInfo.get(4);
					clientMultiplayer.setGroupInfo(groupInfo, hostname);
					clientMultiplayer.c.show(clientMultiplayer.panelPlay, "card1");
					Client.messageToServer = "INTERRUPT" + "\n";
					synchronized(writeLockObj) {
						writeLockObj.notify();
					}
					util.finishSession(inputThread, outputThread);
					ClientSinglePlayer.this.dispose();	
				}
			}
		});
		//=======================================================//
		
		//======== NÚT BACK Ở PANEL HIGH SCORE ON CLICK =========//
		hsBackButton.addMouseListener(new MouseAdapter() {
			public void mouseClicked(MouseEvent e) {
				CardLayout card = (CardLayout) playPanel.getLayout();
				card.show(playPanel,"card1");
			}
		});
		//=======================================================//
		
		//=============== START SINGLE PLAY GAME ================//
		btnStartGame.addActionListener(new ActionListener() {
			public void actionPerformed(ActionEvent e) {
				totalScore = 0; ans = 0;
				lblCurrentscore.setText(totalScore.toString());
				CardLayout card = (CardLayout) playPanel.getLayout();
				card.show(playPanel,"card3");
				randomQuestField();
			}
		});
		//=======================================================//
		
		//=========== CLICK XEM HIGHSCORE - CHƯA LÀM ============//
		btnHighScore.addActionListener(new ActionListener() {
			public void actionPerformed(ActionEvent e) {
				setHighScore();
				CardLayout card = (CardLayout) playPanel.getLayout();
				card.show(playPanel, "card4");
			}
		});
		//=======================================================//
		
		//================= CLICK EXIT BUTTON ===================//
		btnExit.addActionListener(new ActionListener() {
			public void actionPerformed(ActionEvent e) {
				protocol.setState(Protocol.EXIT);							// STATE - EXIT
				Client.messageToServer = protocol.getMessageForm() + "\n";	// LẤY FORM MESSAGE
				synchronized(writeLockObj) {
					writeLockObj.notify();									// NOTIFY LẦN 1 WRITELOCKOJB
				}
				try {	
					Thread.sleep(100);										// SLEEP 0.1 S ĐỂ DÙNG NOTIFY LẦN 2 TRÊN CÙNG 1 OBJECT
				} catch (InterruptedException e1) {
					
				}
				try {
					connection.close();
					if(inputThread.isAlive() || outputThread.isAlive()) {
						util.finishSession(inputThread, outputThread);
					}
				} catch (IOException e1) { }
				ClientSinglePlayer.this.dispose();
			}
		});
		//=======================================================//
		
		//============= CLICK CÁC BUTTON A B C D ================//
		rdbtnChoiceA.addActionListener(new ActionListener() {
			public void actionPerformed(ActionEvent e) {
		        rdbtnChoiceA.setSelected(true);
		        rdbtnChoiceB.setSelected(false);
		        rdbtnChoiceC.setSelected(false);
		        rdbtnChoiceD.setSelected(false);
			}
		});
		
		rdbtnChoiceB.addActionListener(new ActionListener() {
			public void actionPerformed(ActionEvent e) {
				rdbtnChoiceB.setSelected(true);
		        rdbtnChoiceA.setSelected(false);
		        rdbtnChoiceC.setSelected(false);
		        rdbtnChoiceD.setSelected(false);
			}
		});
		
		rdbtnChoiceC.addActionListener(new ActionListener() {
			public void actionPerformed(ActionEvent e) {
				rdbtnChoiceC.setSelected(true);
		        rdbtnChoiceA.setSelected(false);
		        rdbtnChoiceB.setSelected(false);
		        rdbtnChoiceD.setSelected(false);
			}
		});
		
		rdbtnChoiceD.addActionListener(new ActionListener() {
			public void actionPerformed(ActionEvent e) {
				rdbtnChoiceD.setSelected(true);
		        rdbtnChoiceA.setSelected(false);
		        rdbtnChoiceB.setSelected(false);
		        rdbtnChoiceC.setSelected(false);
			}
		});
		//=======================================================//
		
		//=========== ẤN NÚT SUBMIT GỬI CÂU TRẢ LỜI =============//
		btnSubmit.addActionListener(new ActionListener() {
			public void actionPerformed(ActionEvent e) {
				if (rdbtnChoiceA.isSelected()) {
		            if(questionInfo.get(7).equals("A")) {
		                JOptionPane.showMessageDialog(null, "Correct answer!", "Correct answer!", JOptionPane.INFORMATION_MESSAGE);
		                randomQuestField();
		                totalScore += score; ans++;
		                lblCurrentscore.setText(totalScore.toString());
		                CardLayout card = (CardLayout) playPanel.getLayout();
		                card.show(playPanel, "card3");
		            } else {
		            	JOptionPane.showMessageDialog(null, "Incorrect answer!", "Incorrect answer!", JOptionPane.INFORMATION_MESSAGE);
		            	lblFinalscore.setText(totalScore.toString());
		            	questionsAnsweredLabel.setText(ans.toString());
		            	setScore();
		            	CardLayout card = (CardLayout) playPanel.getLayout();
		                card.show(playPanel, "card6");
		            }
		        }           
				if (rdbtnChoiceB.isSelected()) {
		            if(questionInfo.get(7).equals("B")) {
		                JOptionPane.showMessageDialog(null, "Correct answer!", "Correct answer!", JOptionPane.INFORMATION_MESSAGE);
		                randomQuestField();
		                totalScore += score; ans++;
		                lblCurrentscore.setText(totalScore.toString());
		                CardLayout card = (CardLayout) playPanel.getLayout();
		                card.show(playPanel, "card3");
		            } else {
		            	JOptionPane.showMessageDialog(null, "Incorrect answer!", "Incorrect answer!", JOptionPane.INFORMATION_MESSAGE);
		            	lblFinalscore.setText(totalScore.toString());
		            	questionsAnsweredLabel.setText(ans.toString());
		            	setScore();
		            	CardLayout card = (CardLayout) playPanel.getLayout();
		                card.show(playPanel, "card6");
		            	
		            }
		        }         
				if (rdbtnChoiceC.isSelected()) {
		            if(questionInfo.get(7).equals("C")) {
		                JOptionPane.showMessageDialog(null, "Correct answer!", "Correct answer!", JOptionPane.INFORMATION_MESSAGE);
		                randomQuestField();
		                totalScore += score; ans++;
		                lblCurrentscore.setText(totalScore.toString());
		                CardLayout card = (CardLayout) playPanel.getLayout();
		                card.show(playPanel, "card3");
		            } else {
		            	JOptionPane.showMessageDialog(null, "Incorrect answer!", "Incorrect answer!", JOptionPane.INFORMATION_MESSAGE);
		            	lblFinalscore.setText(totalScore.toString());
		            	questionsAnsweredLabel.setText(ans.toString());
		            	setScore();
		            	CardLayout card = (CardLayout) playPanel.getLayout();
		                card.show(playPanel, "card6");
		            	
		            }
		        }         
				if (rdbtnChoiceD.isSelected()) {
		            if(questionInfo.get(7).equals("D")) {
		                JOptionPane.showMessageDialog(null, "Correct answer!", "Correct answer!", JOptionPane.INFORMATION_MESSAGE);
		                randomQuestField();
		                totalScore += score; ans++;
		                lblCurrentscore.setText(totalScore.toString());
		                CardLayout card = (CardLayout) playPanel.getLayout();
		                card.show(playPanel, "card3");
		            } else {
		            	JOptionPane.showMessageDialog(null, "Incorrect answer!", "Incorrect answer!", JOptionPane.INFORMATION_MESSAGE);
		            	lblFinalscore.setText(totalScore.toString());
		            	questionsAnsweredLabel.setText(ans.toString());
		            	setScore();
		            	CardLayout card = (CardLayout) playPanel.getLayout();
		                card.show(playPanel, "card6");
		            	
		            }
		        }         
   
			}
		});
		//=======================================================//
		
		//============= LỰA CHỌN MỨC ĐỘ CÂU HỎI =================//
		btnEasy.addActionListener(new ActionListener() {
			public void actionPerformed(ActionEvent e) {
				setQuestion("3");
				score = 5;
				CardLayout card = (CardLayout) playPanel.getLayout();
				card.show(playPanel,"card2");
				resetChoiceButton();
			}	
		});

		btnMedium.addActionListener(new ActionListener() {
			public void actionPerformed(ActionEvent e) {
				setQuestion("2");
				score = 10;
				CardLayout card = (CardLayout) playPanel.getLayout();
				card.show(playPanel,"card2");
				resetChoiceButton();
			}
		});

		btnHard.addActionListener(new ActionListener() {
			public void actionPerformed(ActionEvent e) {
				setQuestion("1");
				score = 15;
				CardLayout card = (CardLayout) playPanel.getLayout();
				card.show(playPanel,"card2");
				resetChoiceButton();
			}
		});
		//=======================================================//
		
		//======== KHI ẤN TẮT FRAME BẰNG NÚT X Ở GÓC PHẢI =======//
		addWindowListener(new WindowAdapter() {
			public void windowClosing(WindowEvent e) {
				protocol.setState(Protocol.EXIT);							// STATE - EXIT
				Client.messageToServer = protocol.getMessageForm() + "\n";	// LẤY FORM MESSAGE
				synchronized(writeLockObj) {
					writeLockObj.notify();									// NOTIFY LẦN 1 WRITELOCKOJB
				}
				try {	
					Thread.sleep(100);										// SLEEP 0.1 S ĐỂ DÙNG NOTIFY LẦN 2 TRÊN CÙNG 1 OBJECT
				} catch (InterruptedException e1) {
					
				}
				try {
					connection.close();
					if(inputThread.isAlive() || outputThread.isAlive()) {
						util.finishSession(inputThread, outputThread);
					}
				} catch (IOException e1) { }
				ClientSinglePlayer.this.dispose();
			}
		});
		//=======================================================//
	}
	//=======================================================//
	
	//================= RANDOM QUESTION FIELD ===============//
	public void randomQuestField() {
        switch(new Random().nextInt(4)) {
            case 0: lblQuestiontypelabel.setText("This is an English question.");
            	questionField = "ENG";
                break;
            case 1: lblQuestiontypelabel.setText("This is a Biological question.");
            	questionField = "BIO";
            	break;
            case 2: lblQuestiontypelabel.setText("This is a Geography question.");
            	questionField = "GEO";
                break;
            case 3: lblQuestiontypelabel.setText("This is a Japanese question.");
            	questionField = "JP";
            	break;
        }
    }
	//=======================================================//
	
	//================= LẤY CÂU HỎI TỪ SERVER ===============//
	public void setQuestion(String level) {
		protocol.setState(Protocol.PLAY);
		Client.messageToServer = String.format(protocol.getMessageForm(), level, questionField) + "\n";
		synchronized(writeLockObj) {
			writeLockObj.notify();
		}
		protocol.setState(Protocol.SINGLEPLAY);
		synchronized(readLockObj) {
			try {
				readLockObj.wait();
			} catch (InterruptedException ex) {
				System.out.println("Set Question (wait): " + ex);
			}
		}

		questionInfo = protocol.analyseMessageFromServer(Client.messageFromServer);
		switch(questionInfo.get(0)) {
		case "SUCCESS":
			questionTextArea.setText(questionInfo.get(2));
			rdbtnChoiceA.setText(questionInfo.get(3));
			rdbtnChoiceB.setText(questionInfo.get(4));
			rdbtnChoiceC.setText(questionInfo.get(5));
			rdbtnChoiceD.setText(questionInfo.get(6));
			break;
		case "ERR":
			JOptionPane.showMessageDialog(null, questionInfo.get(1), "ERROR", JOptionPane.WARNING_MESSAGE);
			break;
		}
	}
	//=======================================================//

	//============= SET ONLINE USERS TRÊN LIST ==============//
	public void setOnlineUsers(ArrayList<String> onlineUsers) {
		this.onlineUsers = onlineUsers;
		DefaultListModel<String> model = new DefaultListModel<String> ();
		for(int i=0; i<onlineUsers.size(); i++) {
			model.addElement(onlineUsers.get(i));
		}
		list.setModel(model);
	}
	//=======================================================//
	
	//============ SET PLAYER INFO TRÊN FRAME ===============//
	public void setPlayerInfo (ArrayList<String> info) {
		this.playerInfo = info;
		lblNamelabel.setText(playerInfo.get(1));
		lblEmailLabel.setText(playerInfo.get(2));
		lblPhonelabel.setText(playerInfo.get(3));
		lblUsername.setText(playerInfo.get(4));
		svPortLabel.setText("Server Port: " + String.valueOf(connection.getPort()));
		svNameLabel.setText("Server Address: " + connection.getLocalAddress().toString());
		clPortLabel.setText("Client Port: " + String.valueOf(connection.getLocalPort()));
		clNameLabel.setText("Client Address: " + connection.getLocalSocketAddress());
	}
	//=======================================================//
	
	//=============== RESET 4 BUTTON ĐÁP ÁN =================//
	public void resetChoiceButton() {
		rdbtnChoiceA.setSelected(false);       
		rdbtnChoiceB.setSelected(false);       
		rdbtnChoiceC.setSelected(false);       
		rdbtnChoiceD.setSelected(false);    
	}
	//=======================================================//
	
	//=========== TẠO FRAME CLIENT SINGLE PLAYER ============//
	public void createClientSinglePlayerFrame() {
		setResizable(false);
		setSize(new Dimension(1000, 600));
		setLocationRelativeTo(null);
		setTitle("Multiple Choice Queston Test");
		setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);
		
		invitePanel = new JPanel();
		panelOnlineList = new JPanel();
		infoPanel = new JPanel();
		panel = new JPanel();
		playPanel = new JPanel();
		startPanel = new JPanel();
		levelPanel = new JPanel();
		gamePanel = new JPanel();
		highScorePanel = new JPanel();
		endPanel = new JPanel();
		historyPanel = new JPanel();
		endPanel.setOpaque(false);
		menuBar = new JMenuBar();
		mnGame = new JMenu("Game");
		mnHelp = new JMenu("Help");
		separator = new JSeparator();
		mntmHowToPlay = new JMenuItem("How to play");
		mntmHowToPlay.addActionListener(new ActionListener() {
			public void actionPerformed(ActionEvent arg0) {
				ClientRules clientRule = new ClientRules();
				clientRule.setVisible(true);
			}
		});
		mntmAbout = new JMenuItem("About");
		mntmExit = new JMenuItem("Exit");
		mntmNewGame = new JMenuItem("New Game");
		mntmNewGame.addActionListener(new ActionListener() {
			public void actionPerformed(ActionEvent arg0) {
				CardLayout card = (CardLayout) playPanel.getLayout();
				card.show(playPanel, "card1");
			}
		});
		mntmHighScore = new JMenuItem("High Score");
		mntmHighScore.addActionListener(new ActionListener() {
			public void actionPerformed(ActionEvent e) {
				setHighScore();
				CardLayout card = (CardLayout) playPanel.getLayout();
				card.show(playPanel, "card4");
			}
		});
		btnEasy = new JButton("Easy");
		btnMedium = new JButton("Medium");;
		btnHard = new JButton("Hard");
		btnSubmit = new JButton("Submit");
		hsBackButton = new JButton("Back");	
		btnStartGame = new JButton("Start Game");
		btnHighScore = new JButton("High Score");
		btnExit = new JButton("Exit");
		btnHistory = new JButton("History");
		//=======================HISTORY VIEW===================//
		btnHistory.addActionListener(new ActionListener() {
			public void actionPerformed(ActionEvent arg0) {
				setHighScore();
				CardLayout card = (CardLayout) playPanel.getLayout();
				card.show(playPanel, "card4");
			}
		});
		//======================================================//
		btnLogOut = new JButton("Log out");
		btnInvite = new JButton("Invite");
		lblUsername = new JLabel("usernameLabel");
		lblQuestiontypelabel = new JLabel("questionTypeLabel");
		lblWelcome = new JLabel("Welcome");
		lblNamelabel = new JLabel("nameLabel");
		lblEmailLabel = new JLabel("emailLabel");
		lblPhonelabel = new JLabel("phoneLabel");
		svNameLabel = new JLabel("portLabel");
		svPortLabel = new JLabel("New label");
		clNameLabel = new JLabel("Client Name Label");
		clPortLabel = new JLabel("Client Port Label");
		lblWhichLevelYou = new JLabel("Which level you want to play ?");
		rdbtnChoiceA = new JRadioButton("Choice A");
		rdbtnChoiceB = new JRadioButton("Choice B");
		rdbtnChoiceC = new JRadioButton("Choice C");
		rdbtnChoiceD = new JRadioButton("Choice D");
		list = new JList<String>();
		menuBar = new JMenuBar();
		mnGame = new JMenu("Game");
		mnHelp = new JMenu("Help");
		separator = new JSeparator();
		
		getContentPane().setLayout(null);
		getContentPane().add(menuBar);
		bgPanel.setComponentOrientation(ComponentOrientation.LEFT_TO_RIGHT);
		getContentPane().add(bgPanel);
		
		menuBar.add(mnGame);
		menuBar.setBounds(0, 0, 994, 21);
		menuBar.add(mnHelp);
		
		mnGame.add(mntmNewGame);
		mnGame.add(mntmHighScore);
		mnGame.add(separator);
		mnGame.add(mntmExit);
		mnHelp.add(mntmHowToPlay);
		mnHelp.add(mntmAbout);
		
		mntmNewGame.setAccelerator(KeyStroke.getKeyStroke(KeyEvent.VK_F2, 0));
		mntmHighScore.setAccelerator(KeyStroke.getKeyStroke(KeyEvent.VK_F3, 0));
		mntmExit.setAccelerator(KeyStroke.getKeyStroke(KeyEvent.VK_F4, InputEvent.ALT_MASK));
		mntmHowToPlay.setAccelerator(KeyStroke.getKeyStroke(KeyEvent.VK_F4, 0));
		mntmAbout.setAccelerator(KeyStroke.getKeyStroke(KeyEvent.VK_F5, 0));
		
		bgPanel.setBounds(0, 24, 994, 548);
		bgPanel.setLayout(null);
		bgPanel.add(infoPanel);
		bgPanel.add(panel);
		bgPanel.add(svNameLabel);
		bgPanel.add(svPortLabel);
		bgPanel.add(clNameLabel);
		bgPanel.add(clPortLabel);

		infoPanel.setOpaque(false);
		infoPanel.setBounds(8, 0, 148, 525);
		infoPanel.setFont(new Font("Tahoma", Font.PLAIN, 11));
		infoPanel.setBorder(new TitledBorder(UIManager.getBorder("TitledBorder.border"), "Infomation", TitledBorder.LEFT, TitledBorder.ABOVE_TOP, new Font("Segoe Print", Font.BOLD, 15), null));panel.setBorder(new TitledBorder(UIManager.getBorder("TitledBorder.border"), "Multi Choice Test", TitledBorder.LEADING, TitledBorder.ABOVE_TOP, new Font("Segoe Print", Font.BOLD, 15), null));
		infoPanel.setLayout(null);
		panel.setOpaque(false);
		panel.setBounds(168, 0, 606, 525);
		panel.setFont(new Font("Tahoma", Font.PLAIN, 16));
		panel.setBorder(new TitledBorder(UIManager.getBorder("TitledBorder.border"), "Multi Choice Test", TitledBorder.LEADING, TitledBorder.ABOVE_TOP, new Font("Segoe Print", Font.BOLD, 15), null));		
		panel.setLayout(new BorderLayout(0, 0));
		
		panel.add(playPanel);
		infoPanel.add(lblWelcome);
		infoPanel.add(lblNamelabel);
		infoPanel.add(lblEmailLabel);
		infoPanel.add(lblPhonelabel);
		infoPanel.add(btnHistory);	
		infoPanel.add(btnLogOut);
		infoPanel.add(lblUsername);
		btnHistory.setRequestFocusEnabled(false);
		btnLogOut.setRequestFocusEnabled(false);
		lblWelcome.setFont(new Font("Segoe Print", Font.BOLD, 17));
		lblNamelabel.setFont(new Font("Segoe Print", Font.PLAIN, 14));
		lblEmailLabel.setFont(new Font("Segoe Print", Font.PLAIN, 14));
		lblPhonelabel.setFont(new Font("Segoe Print", Font.PLAIN, 14));
		btnHistory.setFont(new Font("Segoe Print", Font.PLAIN, 16));
		btnLogOut.setFont(new Font("Segoe Print", Font.PLAIN, 16));
		lblWelcome.setHorizontalAlignment(SwingConstants.CENTER);
		lblNamelabel.setHorizontalAlignment(SwingConstants.CENTER);
		lblEmailLabel.setHorizontalAlignment(SwingConstants.CENTER);
		lblPhonelabel.setHorizontalAlignment(SwingConstants.CENTER);
		lblWelcome.setBounds(6, 52, 136, 30);
		lblNamelabel.setBounds(6, 156, 128, 30);
		lblEmailLabel.setBounds(6, 198, 128, 30);
		lblPhonelabel.setBounds(6, 253, 128, 30);
		btnHistory.setBounds(23, 391, 103, 39);
		btnLogOut.setBounds(23, 445, 103, 39);
		svNameLabel.setBounds(38, 526, 169, 16);
		svPortLabel.setBounds(219, 526, 127, 16);
		clNameLabel.setBounds(526, 526, 201, 16);
		clPortLabel.setBounds(796, 526, 142, 16);
		btnHistory.setBackground(UIManager.getColor("ArrowButton.background"));
		btnLogOut.setBackground(UIManager.getColor("ArrowButton.background"));
		lblUsername.setHorizontalAlignment(SwingConstants.CENTER);
		lblUsername.setFont(new Font("Segoe Print", Font.PLAIN, 14));
		lblUsername.setBounds(6, 114, 128, 30);
		
		playPanel.setOpaque(false);
		playPanel.setLayout(cl);	
		playPanel.add(startPanel, "card1");
		playPanel.add(gamePanel, "card2");
		playPanel.add(levelPanel, "card3");
		playPanel.add(highScorePanel, "card4");
		playPanel.add(endPanel, "card6");
		playPanel.add(historyPanel, "card7");
		startPanel.add(btnStartGame);
		startPanel.add(btnHighScore);
		startPanel.add(btnExit);
		
		levelPanel.setOpaque(false);
		gamePanel.setOpaque(false);
		startPanel.setOpaque(false);
		highScorePanel.setOpaque(false);
		historyPanel.setOpaque(false);
		startPanel.setLayout(null);
		gamePanel.setLayout(null);
		highScorePanel.setLayout(null);
		levelPanel.setLayout(null);
		btnStartGame.setBackground(UIManager.getColor("ArrowButton.background"));
		btnStartGame.setRequestFocusEnabled(false);
		btnStartGame.setFocusPainted(false);
		btnStartGame.setFocusCycleRoot(true);
		btnHighScore.setBackground(UIManager.getColor("ArrowButton.background"));
		btnHighScore.setFocusCycleRoot(true);
		btnHighScore.setFocusPainted(false);
		btnHighScore.setRequestFocusEnabled(false);
		btnExit.setBackground(UIManager.getColor("ArrowButton.background"));
		btnExit.setRequestFocusEnabled(false);
		btnExit.setFocusCycleRoot(true);
		btnExit.setFocusPainted(false);
		
		hsScrollPane = new JScrollPane();
		hsScrollPane.setBounds(16, 21, 545, 376);
		highScorePanel.add(hsScrollPane);
		highScoreTable.setOpaque(false);
		hsScrollPane.setViewportView(highScoreTable);
		highScoreTable.setCursor(new java.awt.Cursor(java.awt.Cursor.DEFAULT_CURSOR));
		highScoreTable.setDragEnabled(true);
		highScorePanel.add(hsBackButton);
		questionTextArea.setLineWrap(true);
		questionTextArea.setEditable(false);
		
		historyScrollPane = new JScrollPane();
		historyScrollPane.setBounds(16, 21, 545, 376);
		historyPanel.add(historyScrollPane);
		historyTable.setOpaque(false);
		historyScrollPane.setViewportView(historyTable);
		historyTable.setCursor(new java.awt.Cursor(java.awt.Cursor.DEFAULT_CURSOR));
		historyTable.setDragEnabled(true);
		
		gamePanel.add(questionTextArea);
		gamePanel.add(rdbtnChoiceA);
		gamePanel.add(rdbtnChoiceB);
		gamePanel.add(rdbtnChoiceC);
		gamePanel.add(rdbtnChoiceD);
		gamePanel.add(btnSubmit);
		levelPanel.add(btnEasy);
		levelPanel.add(btnMedium);
		levelPanel.add(btnHard);
		levelPanel.add(lblWhichLevelYou);
		levelPanel.add(lblQuestiontypelabel);
		
		btnStartGame.setFont(new Font("Segoe Print", Font.BOLD, 15));
		btnHighScore.setFont(new Font("Segoe Print", Font.BOLD, 15));
		btnExit.setFont(new Font("Segoe Print", Font.BOLD, 15));
		hsBackButton.setFont(new Font("Segoe Print", Font.PLAIN, 15));
		btnEasy.setFont(new Font("Segoe Print", Font.PLAIN, 15));
		btnMedium.setFont(new Font("Segoe Print", Font.PLAIN, 15));
		btnHard.setFont(new Font("Segoe Print", Font.PLAIN, 15));
		lblWhichLevelYou.setFont(new Font("Segoe Print", Font.PLAIN, 26));
		lblQuestiontypelabel.setFont(new Font("Segoe Print", Font.PLAIN, 26));
		
		btnStartGame.setBounds(231, 107, 120, 49);
		btnHighScore.setBounds(231, 196, 122, 49);
		btnExit.setBounds(231, 278, 120, 50);
		hsBackButton.setBounds(234, 413, 117, 28);
		questionTextArea.setBounds(50, 67, 497, 108);
		rdbtnChoiceA.setBounds(120, 207, 427, 23);
		rdbtnChoiceB.setBounds(120, 248, 427, 23);
		rdbtnChoiceC.setBounds(120, 294, 427, 23);
		rdbtnChoiceD.setBounds(120, 341, 427, 23);
		btnSubmit.setBounds(253, 418, 89, 23);
		btnEasy.setBounds(74, 270, 109, 33);
		btnMedium.setBounds(242, 271, 97, 33);
		btnHard.setBounds(407, 271, 97, 33);
		lblWhichLevelYou.setBounds(74, 159, 430, 55);
		lblQuestiontypelabel.setBounds(74, 93, 430, 47);
		
		rdbtnChoiceA.setContentAreaFilled(false);
		rdbtnChoiceA.setSelected(false);
		rdbtnChoiceB.setSelected(false);
		rdbtnChoiceC.setSelected(false);
		rdbtnChoiceD.setSelected(false);
		
		lblCurrentScore = new JLabel("Score:");
		lblCurrentScore.setFont(new Font("Segoe Print", Font.PLAIN, 15));
		lblCurrentScore.setHorizontalAlignment(SwingConstants.CENTER);
		lblCurrentScore.setBounds(377, 29, 53, 27);
		gamePanel.add(lblCurrentScore);
		
		lblCurrentscore = new JLabel("currentScore");
		lblCurrentscore.setFont(new Font("Segoe Print", Font.BOLD, 15));
		lblCurrentscore.setBounds(470, 29, 53, 27);
		gamePanel.add(lblCurrentscore);
		lblWhichLevelYou.setHorizontalAlignment(SwingConstants.CENTER);
		lblQuestiontypelabel.setHorizontalAlignment(SwingConstants.CENTER);
		tableTitle1.add("Username");
		tableTitle1.add("Fullname");
		tableTitle1.add("Questions Answered");
		tableTitle1.add("Score");
		
		tableTitle2.add("Username");
		tableTitle2.add("Date Played");
		tableTitle2.add("Questions Answered");
		tableTitle2.add("Score");
		
		invitePanel.setOpaque(false);
		playPanel.add(invitePanel, "card5");
		invitePanel.setLayout(null);
		lblInvite = new JLabel("%s invited you into a group and play, %s");
		lblInvite.setFont(new Font("Segoe Print", Font.PLAIN, 18));
		lblInvite.setBorder(new TitledBorder(null, "", TitledBorder.LEADING, TitledBorder.TOP, null, null));
		lblInvite.setHorizontalTextPosition(SwingConstants.CENTER);
		lblInvite.setHorizontalAlignment(SwingConstants.CENTER);
		lblInvite.setBounds(23, 112, 534, 98);
		invitePanel.add(lblInvite);
		btnAccept = new JButton("Accept");
		btnAccept.setFont(new Font("Segoe Print", Font.PLAIN, 14));
		btnAccept.setBounds(158, 254, 90, 28);
		invitePanel.add(btnAccept);
		btnDecline = new JButton("Decline");
		btnDecline.setFont(new Font("Segoe Print", Font.PLAIN, 14));
		btnDecline.setBounds(340, 254, 90, 28);
		invitePanel.add(btnDecline);
		panelOnlineList.setOpaque(false);
		panelOnlineList.setBorder(new TitledBorder(null, "Online User", TitledBorder.LEADING, TitledBorder.ABOVE_TOP, new Font("Segoe Print", Font.BOLD, 15), null));
		panelOnlineList.setBounds(786, 0, 202, 525);

		btnDecline.setFont(new Font("Segoe Print", Font.PLAIN, 14));
		btnDecline.setBounds(340, 254, 90, 28);
		invitePanel.add(btnDecline);
		
		endPanel.setLayout(null);
		
		lblNewLabel_2 = new JLabel("Your answer was wrong!");
		lblNewLabel_2.setHorizontalAlignment(SwingConstants.CENTER);
		lblNewLabel_2.setFont(new Font("Segoe Print", Font.PLAIN, 15));
		lblNewLabel_2.setBounds(174, 100, 280, 22);
		endPanel.add(lblNewLabel_2);
		
		lblQuestionsAnswered = new JLabel("Questions Answered:");
		lblQuestionsAnswered.setFont(new Font("Segoe Print", Font.PLAIN, 15));
		lblQuestionsAnswered.setBounds(174, 173, 162, 22);
		endPanel.add(lblQuestionsAnswered);
		
		questionsAnsweredLabel = new JLabel("lblQuestionAnswered");
		questionsAnsweredLabel.setFont(new Font("Segoe Print", Font.PLAIN, 15));
		questionsAnsweredLabel.setBounds(366, 173, 56, 22);
		endPanel.add(questionsAnsweredLabel);
		
		lblScore = new JLabel("Score:");
		lblScore.setFont(new Font("Segoe Print", Font.PLAIN, 15));
		lblScore.setBounds(218, 241, 56, 22);
		endPanel.add(lblScore);
		
		lblFinalscore = new JLabel("finalScore");
		lblFinalscore.setFont(new Font("Segoe Print", Font.PLAIN, 15));
		lblFinalscore.setBounds(366, 241, 62, 22);
		endPanel.add(lblFinalscore);
		
		btnBack = new JButton("Back");
		btnBack.addActionListener(new ActionListener() {
			public void actionPerformed(ActionEvent arg0) {
				CardLayout card = (CardLayout) playPanel.getLayout();
				card.show(playPanel,"card1");
			}
		});
		btnBack.setFont(new Font("Segoe Print", Font.PLAIN, 15));
		btnBack.setBounds(257, 369, 89, 35);
		endPanel.add(btnBack);
		
		
		historyPanel.setLayout(null);
		
		btnBack_1 = new JButton("Back");
		btnBack_1.addActionListener(new ActionListener() {
			public void actionPerformed(ActionEvent arg0) {
				CardLayout card = (CardLayout) playPanel.getLayout();
				card.show(playPanel, "card1");
			}
		});
		btnBack_1.setFont(new Font("Segoe Print", Font.PLAIN, 15));
		btnBack_1.setBounds(254, 404, 89, 35);
		historyPanel.add(btnBack_1);
		panelOnlineList.setOpaque(false);
		panelOnlineList.setBorder(new TitledBorder(null, "Online User", TitledBorder.LEADING, TitledBorder.ABOVE_TOP, new Font("Segoe Print", Font.BOLD, 15), null));
		panelOnlineList.setBounds(786, 0, 202, 525);
		
		bgPanel.add(panelOnlineList);
		panelOnlineList.setLayout(null);
		scrollPane.setBounds(26, 52, 152, 187);	
		panelOnlineList.add(scrollPane);
		panelOnlineList.add(btnInvite);
		list.setRequestFocusEnabled(false);
		list.setFocusCycleRoot(true);
		list.setBorder(new CompoundBorder());
		scrollPane.setViewportView(list);
		btnInvite.setFocusCycleRoot(true);
		btnInvite.setFocusPainted(false);
		btnInvite.setRequestFocusEnabled(false);
		btnInvite.setFont(new Font("Segoe Print", Font.PLAIN, 16));
		btnInvite.setBorder(new CompoundBorder());
		btnInvite.setBounds(56, 273, 90, 28);
	}
	//=======================================================//

	//==================== SET HIGH SCORE ===================//
	public void setHighScore() {
		protocol.setState(Protocol.GET_HIGHSCORE);
		Client.messageToServer = protocol.getMessageForm() + "\n";
		protocol.setState(Protocol.SINGLEPLAY);
		synchronized(writeLockObj) {
			writeLockObj.notify();
		}
		synchronized(readLockObj) {
			try {
				readLockObj.wait();
			} catch (InterruptedException ex) { }
		}
		highScoreTable.setModel(new DefaultTableModel(tableRecord1, tableTitle1));
	}
	//=======================================================//
	
	//==================== SUBMIT SCORE ===================//
	public void setScore() {
		protocol.setState(Protocol.SINGLESUBMIT);
		Client.messageToServer = String.format(protocol.getMessageForm(), playerInfo.get(4), ans, totalScore) + "\n";
		protocol.setState(Protocol.SINGLEPLAY);
		synchronized(writeLockObj) {
			writeLockObj.notify();
		}
	}	
	//=======================================================//

	//==================== SET HISTORY ======================//
	public void setHistory() {
		protocol.setState(Protocol.GET_HISTORY);
		Client.messageToServer = String.format(protocol.getMessageForm(), playerInfo.get(4)) + "\n";
		protocol.setState(Protocol.SINGLEPLAY);
		synchronized(writeLockObj) {
			writeLockObj.notify();
		}
		synchronized(readLockObj) {
			try {
				readLockObj.wait();
			} catch (InterruptedException ex) { }
		}
		historyTable.setModel(new DefaultTableModel(tableRecord2, tableTitle2));
	}
	
}

	
